-module(demo).
-export([ create/1, create2/1, reverse_create/1, print_num/1, print_even/1, filter/2, concatenate/1, quicksort/1, dump/1, average/1 , member/2]).
-complie(export_all).




-spec dump(List::list()) -> List2::list().
% -spec sum(List::list()) -> number().
% -spec len(List::list()) -> non_neg_integer().
-spec member(Term::term(), List::list()) -> boolean().
-spec average(List::list()) -> float().
-spec average_acc(List, Sum, Length) -> float() when
	List::list(),
	Sum::float(),
	Length::non_neg_integer().

average([]) -> 0;
average(List) when is_list(List) ->
	average_acc(List, 0, 0).

average_acc([], Sum, Length) ->
	Sum/Length;
average_acc([H|Tail], Sum, Length) ->
	average_acc(Tail, H+Sum, 1+Length).



member(_, []) -> false;
member(Term, [Head|Tail]) ->
	case Term==Head of
		true -> true;
		false -> member(Term, Tail)
	end.

% member(_, []) -> false;
% member(H, [H|_]) -> true;
% member(H, [_|T]) -> member(H, T).



dump([]) -> [];
dump([H|Tail] = List ) when is_list(List) ->
	[H+1|dump(Tail)].

% average(List) -> sum(List) / len(List).
% sum([]) -> 0;
% sum([Head|Tail]) -> Head + sum(Tail).
% len([]) -> 0;
% len([_|Tail]) -> 1+len(Tail).

create(N) when N>0 ->
	[N|create(N-1)];
	create(0) -> [] .

create2(N) when N>0 ->
	create2(N-1)++[N];
	create2(0) -> [].

reverse_create(N) when N>0 ->
	List = create(N),
	reverse(List).

reverse(List)->
	reverse(List,[]).
reverse([H|T], Rlist) ->
	reverse(T,[H|Rlist]);
	reverse([], Rlist) ->
		Rlist.

print_num(N) when N>1 ->
	I = 1,
	print_num(I, N).
print_num(I, N) when N>1, I<N ->
	io:format("Number:~p~n", [I]),
	print_num(I+1,N);
	print_num(N,N) ->
		io:format("Number:~p~n",[N]).


print_even(N) when N>1 ->
	I = 2,
	case N rem 2 == 0 of
		true ->
			print_even(I, N);
		false ->
			print_even(I, N-1)
	end.
print_even(I, N) when I<N, N rem 2 == 0 ->
	io:format("Number:~p~n", [I]),
	print_even(I+2,N);
print_even(N,N) when N rem 2 == 0 ->
	io:format("Number:~p~n",[N]).

filter(List, N) when is_list(List), N>0 ->
	[X || X <- List, X=<N].

concatenate(List) when is_list(List), List=/=[] ->
	[Head|Tail] = List,
	if
		not is_list(Head) , not is_list(Tail) ->
			List;
		not is_list(Head) , is_list(Tail) ->
			[Head|concatenate(Tail)];
		is_list(Head) , not is_list(Tail) ->
			concatenate(Head)++Tail;
		is_list(Head) , is_list(Tail) ->
			concatenate(Head)++concatenate(Tail)
	end;
	concatenate([]) ->
		[].

quicksort([]) -> [];
quicksort([Head|Tail]) ->
	quicksort(Tail,Head,[],[]).
quicksort([Head|Tail], FirstHead, ListLeft, ListRight) when Head>FirstHead ->
	quicksort(Tail, FirstHead, ListLeft, [Head|ListRight]);
quicksort([Head|Tail], FirstHead, ListLeft, ListRight) when Head=<FirstHead ->
	quicksort(Tail, FirstHead, [Head|ListLeft], ListRight);
quicksort([],Head,ListLeft,ListRight) ->
	ListLeft1 = quicksort(ListLeft),
	ListRight1 = quicksort(ListRight),
	ListLeft1++[Head]++ListRight1.